package com.fortune.app.models;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Random;
import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.Date;
import java.util.Locale;

/**
 * 吉凶方位指南系统实现类
 */
public class DirectionGuide {
    private Map<String, String> directions;
    private Map<String, String> elements;
    private Map<String, String> elementRelations;
    
    public DirectionGuide() {
        initDirections();
        initElements();
        initElementRelations();
    }
    
    /**
     * 初始化方位数据
     */
    private void initDirections() {
        directions = new HashMap<>();
        directions.put("east", "东");
        directions.put("south", "南");
        directions.put("west", "西");
        directions.put("north", "北");
        directions.put("northeast", "东北");
        directions.put("southeast", "东南");
        directions.put("southwest", "西南");
        directions.put("northwest", "西北");
        directions.put("center", "中");
    }
    
    /**
     * 初始化五行数据
     */
    private void initElements() {
        elements = new HashMap<>();
        elements.put("wood", "木");
        elements.put("fire", "火");
        elements.put("earth", "土");
        elements.put("metal", "金");
        elements.put("water", "水");
    }
    
    /**
     * 初始化五行相生相克关系
     */
    private void initElementRelations() {
        elementRelations = new HashMap<>();
        // 相生关系
        elementRelations.put("wood_fire", "生"); // 木生火
        elementRelations.put("fire_earth", "生"); // 火生土
        elementRelations.put("earth_metal", "生"); // 土生金
        elementRelations.put("metal_water", "生"); // 金生水
        elementRelations.put("water_wood", "生"); // 水生木
        
        // 相克关系
        elementRelations.put("wood_earth", "克"); // 木克土
        elementRelations.put("earth_water", "克"); // 土克水
        elementRelations.put("water_fire", "克"); // 水克火
        elementRelations.put("fire_metal", "克"); // 火克金
        elementRelations.put("metal_wood", "克"); // 金克木
    }
    
    /**
     * 根据生日和日期计算吉凶方位
     * 
     * @param birthDate 用户生日，格式为"YYYY-MM-DD"
     * @param targetDate 目标日期，格式为"YYYY-MM-DD"，默认为当天
     * @return 吉凶方位结果
     */
    public Map<String, Object> calculateDirections(String birthDate, String targetDate) {
        try {
            // 如果未指定目标日期，使用当前日期
            if (targetDate == null || targetDate.isEmpty()) {
                SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd", Locale.CHINA);
                targetDate = dateFormat.format(new Date());
            }
            
            SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd", Locale.CHINA);
            Date birthDt = dateFormat.parse(birthDate);
            Date targetDt = dateFormat.parse(targetDate);
            
            Calendar birthCal = Calendar.getInstance();
            Calendar targetCal = Calendar.getInstance();
            birthCal.setTime(birthDt);
            targetCal.setTime(targetDt);
            
            // 计算生肖
            String[] chineseZodiac = {"鼠", "牛", "虎", "兔", "龙", "蛇", "马", "羊", "猴", "鸡", "狗", "猪"};
            int zodiacIndex = (birthCal.get(Calendar.YEAR) - 4) % 12;
            String zodiac = chineseZodiac[zodiacIndex];
            
            // 计算用户的五行属性（简化版，实际应基于八字）
            String userElement = calculateUserElement(birthCal);
            
            // 计算当日五行属性
            String dayElement = calculateDayElement(targetCal);
            
            // 设置随机种子，确保结果的一致性
            int seed = birthCal.get(Calendar.YEAR) * 10000 + 
                       birthCal.get(Calendar.MONTH) * 100 + 
                       birthCal.get(Calendar.DAY_OF_MONTH) +
                       targetCal.get(Calendar.YEAR) * 10000 + 
                       targetCal.get(Calendar.MONTH) * 100 + 
                       targetCal.get(Calendar.DAY_OF_MONTH);
            
            Random random = new Random(seed);
            
            // 计算吉凶方位
            Map<String, Object> luckyDirections = calculateLuckyDirections(userElement, dayElement, random);
            Map<String, Object> unluckyDirections = calculateUnluckyDirections(userElement, dayElement, random);
            
            // 生成方位建议
            List<String> advice = generateDirectionAdvice(luckyDirections, unluckyDirections);
            
            // 返回结果
            Map<String, Object> result = new HashMap<>();
            result.put("date", targetDate);
            
            Map<String, Object> userInfo = new HashMap<>();
            userInfo.put("birth_date", birthDate);
            userInfo.put("zodiac", zodiac);
            userInfo.put("element", userElement);
            result.put("user_info", userInfo);
            
            result.put("day_element", dayElement);
            result.put("lucky_directions", luckyDirections);
            result.put("unlucky_directions", unluckyDirections);
            result.put("advice", advice);
            
            return result;
        } catch (Exception e) {
            e.printStackTrace();
            return new HashMap<>();
        }
    }
    
    /**
     * 计算用户的五行属性（简化版）
     */
    private String calculateUserElement(Calendar birthCal) {
        // 简化版的五行计算，实际应基于八字
        int year = birthCal.get(Calendar.YEAR);
        int month = birthCal.get(Calendar.MONTH) + 1;
        int day = birthCal.get(Calendar.DAY_OF_MONTH);
        
        // 简单算法：根据年份最后一位决定五行
        int lastDigit = year % 10;
        
        if (lastDigit == 0 || lastDigit == 1) {
            return "木";
        } else if (lastDigit == 2 || lastDigit == 3) {
            return "火";
        } else if (lastDigit == 4 || lastDigit == 5) {
            return "土";
        } else if (lastDigit == 6 || lastDigit == 7) {
            return "金";
        } else {
            return "水";
        }
    }
    
    /**
     * 计算当日五行属性
     */
    private String calculateDayElement(Calendar targetCal) {
        // 简化版的当日五行计算
        int dayOfWeek = targetCal.get(Calendar.DAY_OF_WEEK);
        
        switch (dayOfWeek) {
            case Calendar.MONDAY: // 周一
                return "水";
            case Calendar.TUESDAY: // 周二
                return "火";
            case Calendar.WEDNESDAY: // 周三
                return "木";
            case Calendar.THURSDAY: // 周四
                return "木";
            case Calendar.FRIDAY: // 周五
                return "土";
            case Calendar.SATURDAY: // 周六
                return "金";
            case Calendar.SUNDAY: // 周日
                return "火";
            default:
                return "土";
        }
    }
    
    /**
     * 计算吉利方位
     */
    private Map<String, Object> calculateLuckyDirections(String userElement, String dayElement, Random random) {
        Map<String, Object> luckyDirections = new HashMap<>();
        
        // 主吉方：根据五行相生关系
        String mainLuckyDirection = "";
        int luckyScore = 0;
        
        if (userElement.equals("木") && dayElement.equals("火") || 
            userElement.equals("火") && dayElement.equals("土") ||
            userElement.equals("土") && dayElement.equals("金") ||
            userElement.equals("金") && dayElement.equals("水") ||
            userElement.equals("水") && dayElement.equals("木")) {
            // 用户五行生日五行，相生关系最吉
            luckyScore = 5;
            
            if (userElement.equals("木")) {
                mainLuckyDirection = "东";
            } else if (userElement.equals("火")) {
                mainLuckyDirection = "南";
            } else if (userElement.equals("土")) {
                mainLuckyDirection = "中";
            } else if (userElement.equals("金")) {
                mainLuckyDirection = "西";
            } else if (userElement.equals("水")) {
                mainLuckyDirection = "北";
            }
        } else if (dayElement.equals("木") && userElement.equals("火") || 
                  dayElement.equals("火") && userElement.equals("土") ||
                  dayElement.equals("土") && userElement.equals("金") ||
                  dayElement.equals("金") && userElement.equals("水") ||
                  dayElement.equals("水") && userElement.equals("木")) {
            // 日五行生用户五行，次吉
            luckyScore = 4;
            
            if (dayElement.equals("木")) {
                mainLuckyDirection = "东";
            } else if (dayElement.equals("火")) {
                mainLuckyDirection = "南";
            } else if (dayElement.equals("土")) {
                mainLuckyDirection = "中";
            } else if (dayElement.equals("金")) {
                mainLuckyDirection = "西";
            } else if (dayElement.equals("水")) {
                mainLuckyDirection = "北";
            }
        } else if (userElement.equals(dayElement)) {
            // 五行相同，中吉
            luckyScore = 3;
            
            if (userElement.equals("木")) {
                mainLuckyDirection = "东南";
            } else if (userElement.equals("火")) {
                mainLuckyDirection = "东";
            } else if (userElement.equals("土")) {
                mainLuckyDirection = "东北";
            } else if (userElement.equals("金")) {
                mainLuckyDirection = "西北";
            } else if (userElement.equals("水")) {
                mainLuckyDirection = "西南";
            }
        } else {
            // 其他情况，随机选择一个方位
            luckyScore = 2;
            String[] allDirections = {"东", "南", "西", "北", "东北", "东南", "西南", "西北"};
            mainLuckyDirection = allDirections[random.nextInt(allDirections.length)];
        }
        
        // 次吉方：随机选择两个其他方位
        List<String> secondaryLuckyDirections = new ArrayList<>();
        String[] allDirections = {"东", "南", "西", "北", "东北", "东南", "西南", "西北"};
        
        for (int i = 0; i < 2; i++) {
            String direction;
            do {
                direction = allDirections[random.nextInt(allDirections.length)];
            } while (direction.equals(mainLuckyDirection) || secondaryLuckyDirections.contains(direction));
            
            secondaryLuckyDirections.add(direction);
        }
        
        // 吉时：根据五行属性选择
        String luckyTime = "";
        if (userElement.equals("木")) {
            luckyTime = "上午7-9点";
        } else if (userElement.equals("火")) {
            luckyTime = "上午11点-下午1点";
        } else if (userElement.equals("土")) {
            luckyTime = "上午9-11点";
        } else if (userElement.equals("金")) {
            luckyTime = "下午3-5点";
        } else if (userElement.equals("水")) {
            luckyTime = "下午5-7点";
        }
        
        // 吉色：根据五行属性选择
        String luckyColor = "";
        if (userElement.equals("木")) {
            luckyColor = "绿色";
        } else if (userElement.equals("火")) {
            luckyColor = "红色";
        } else if (userElement.equals("土")) {
            luckyColor = "黄色";
        } else if (userElement.equals("金")) {
            luckyColor = "白色";
        } else if (userElement.equals("水")) {
            luckyColor = "蓝色";
        }
        
        luckyDirections.put("main", mainLuckyDirection);
        luckyDirections.put("secondary", secondaryLuckyDirections);
        luckyDirections.put("score", luckyScore);
        luckyDirections.put("time", luckyTime);
        luckyDirections.put("color", luckyColor);
        
        return luckyDirections;
    }
    
    /**
     * 计算凶方位
     */
    private Map<String, Object> calculateUnluckyDirections(String userElement, String dayElement, Random random) {
        Map<String, Object> unluckyDirections = new HashMap<>();
        
        // 主凶方：根据五行相克关系
        String mainUnluckyDirection = "";
        
        if (userElement.equals("木") && dayElement.equals("金") || 
            userElement.equals("金") && dayElement.equals("火") ||
            userElement.equals("火") && dayElement.equals("水") ||
            userElement.equals("水") && dayElement.equals("土") ||
            userElement.equals("土") && dayElement.equals("木")) {
            // 日五行克用户五行，最凶
            
            if (dayElement.equals("木")) {
                mainUnluckyDirection = "东";
            } else if (dayElement.equals("火")) {
                mainUnluckyDirection = "南";
            } else if (dayElement.equals("土")) {
                mainUnluckyDirection = "中";
            } else if (dayElement.equals("金")) {
                mainUnluckyDirection = "西";
            } else if (dayElement.equals("水")) {
                mainUnluckyDirection = "北";
            }
        } else if (userElement.equals("金") && dayElement.equals("木") || 
                  userElement.equals("木") && dayElement.equals("土") ||
                  userElement.equals("土") && dayElement.equals("水") ||
                  userElement.equals("水") && dayElement.equals("火") ||
                  userElement.equals("火") && dayElement.equals("金")) {
            // 用户五行克日五行，次凶
            
            if (userElement.equals("木")) {
                mainUnluckyDirection = "东";
            } else if (userElement.equals("火")) {
                mainUnluckyDirection = "南";
            } else if (userElement.equals("土")) {
                mainUnluckyDirection = "中";
            } else if (userElement.equals("金")) {
                mainUnluckyDirection = "西";
            } else if (userElement.equals("水")) {
                mainUnluckyDirection = "北";
            }
        } else {
            // 其他情况，随机选择一个方位
            String[] allDirections = {"东", "南", "西", "北", "东北", "东南", "西南", "西北"};
            mainUnluckyDirection = allDirections[random.nextInt(allDirections.length)];
        }
        
        // 次凶方：随机选择一个其他方位
        String secondaryUnluckyDirection = "";
        String[] allDirections = {"东", "南", "西", "北", "东北", "东南", "西南", "西北"};
        
        do {
            secondaryUnluckyDirection = allDirections[random.nextInt(allDirections.length)];
        } while (secondaryUnluckyDirection.equals(mainUnluckyDirection));
        
        // 凶时：根据五行相克选择
        String unluckyTime = "";
        if (userElement.equals("木")) {
            unluckyTime = "下午3-5点"; // 金克木
        } else if (userElement.equals("火")) {
            unluckyTime = "下午5-7点"; // 水克火
        } else if (userElement.equals("土")) {
            unluckyTime = "上午7-9点"; // 木克土
        } else if (userElement.equals("金")) {
            unluckyTime = "上午11点-下午1点"; // 火克金
        } else if (userElement.equals("水")) {
            unluckyTime = "上午9-11点"; // 土克水
        }
        
        unluckyDirections.put("main", mainUnluckyDirection);
        unluckyDirections.put("secondary", secondaryUnluckyDirection);
        unluckyDirections.put("time", unluckyTime);
        
        return unluckyDirections;
    }
    
    /**
     * 生成方位建议
     */
    private List<String> generateDirectionAdvice(Map<String, Object> luckyDirections, Map<String, Object> unluckyDirections) {
        List<String> advice = new ArrayList<>();
        
        String mainLuckyDirection = (String) luckyDirections.get("main");
        @SuppressWarnings("unchecked")
        List<String> secondaryLuckyDirections = (List<String>) luckyDirections.get("secondary");
        String luckyTime = (String) luckyDirections.get("time");
        String luckyColor = (String) luckyDirections.get("color");
        
        String mainUnluckyDirection = (String) unluckyDirections.get("main");
        String secondaryUnluckyDirection = (String) unluckyDirections.get("secondary");
        String unluckyTime = (String) unluckyDirections.get("time");
        
        // 吉方建议
        advice.add(String.format("今日主吉方位为%s，次吉方位为%s和%s，重要活动、出行或谈判建议朝这些方向进行。", 
                mainLuckyDirection, 
                secondaryLuckyDirections.get(0), 
                secondaryLuckyDirections.get(1)));
        
        advice.add(String.format("今日吉时为%s，适合在此时段安排重要事务或开展新活动。", luckyTime));
        
        advice.add(String.format("今日吉祥颜色为%s，建议穿着或佩戴此颜色的服饰或饰品，有助于增强运势。", luckyColor));
        
        // 凶方建议
        advice.add(String.format("今日主凶方位为%s，次凶方位为%s，建议避免朝这些方向出行或开展重要活动。", 
                mainUnluckyDirection, secondaryUnluckyDirection));
        
        advice.add(String.format("今日凶时为%s，建议避免在此时段做重要决策或开始新事物。", unluckyTime));
        
        // 其他建议
        advice.add("床头朝向建议与今日吉方一致，有助于提升睡眠质量和恢复精力。");
        
        advice.add("办公桌朝向建议与今日吉方一致，有助于提升工作效率和创造力。");
        
        advice.add("如必须前往凶方，建议佩戴吉祥物或穿着吉祥颜色的衣物以化解不利影响。");
        
        return advice;
    }
}
